<template>
  <div class="lifecycle-hook-demo p-4">
    <div class="space-y-6">
      <!-- 生命周期日志 -->
      <div class="lifecycle-section">
        <h4 class="lifecycle-title">生命周期执行日志</h4>
        <div class="log-container">
          <div
            v-for="(log, index) in lifecycleLogs"
            :key="index"
            class="log-item"
            :class="getLogClass(log.type)"
          >
            <span class="log-time">{{ log.time }}</span>
            <span class="log-type">{{ log.type }}</span>
            <span class="log-message">{{ log.message }}</span>
          </div>
          <div v-if="lifecycleLogs.length === 0" class="text-gray-400 text-sm">
            暂无生命周期日志
          </div>
        </div>
        <button @click="clearLogs" class="btn-clear">清空日志</button>
      </div>

      <!-- 动态组件控制 -->
      <div class="lifecycle-section">
        <h4 class="lifecycle-title">动态组件演示</h4>
        <div class="space-y-3">
          <div class="flex space-x-3">
            <button
              @click="showChild = !showChild"
              class="btn-toggle"
              :class="showChild ? 'btn-red' : 'btn-green'"
            >
              {{ showChild ? '卸载子组件' : '挂载子组件' }}
            </button>
            <button @click="forceUpdate" class="btn-update">强制更新父组件</button>
          </div>

          <!-- 子组件区域 -->
          <div class="child-container">
            <transition name="fade">
              <LifecycleChild
                v-if="showChild"
                :counter="childCounter"
                @lifecycle-event="handleChildLifecycle"
              />
            </transition>
            <div v-if="!showChild" class="no-child">子组件已卸载</div>
          </div>

          <div class="flex space-x-3">
            <button @click="childCounter++" class="btn-small">
              更新子组件 props ({{ childCounter }})
            </button>
            <button @click="childCounter = 0" class="btn-small">重置 props</button>
          </div>
        </div>
      </div>

      <!-- 定时器演示 -->
      <div class="lifecycle-section">
        <h4 class="lifecycle-title">定时器生命周期管理</h4>
        <div class="space-y-3">
          <div class="timer-display">
            <div class="timer-value">{{ timer }}</div>
            <div class="timer-label">秒</div>
          </div>
          <div class="flex justify-center space-x-3">
            <button @click="startTimer" :disabled="isTimerRunning" class="btn-start">
              开始计时
            </button>
            <button @click="stopTimer" :disabled="!isTimerRunning" class="btn-stop">
              停止计时
            </button>
            <button @click="resetTimer" class="btn-reset">重置计时</button>
          </div>
          <div class="text-center text-sm text-gray-600">
            状态: {{ isTimerRunning ? '运行中' : '已停止' }}
          </div>
        </div>
      </div>

      <!-- 事件监听器演示 -->
      <div class="lifecycle-section">
        <h4 class="lifecycle-title">全局事件监听器</h4>
        <div class="space-y-3">
          <div class="event-stats">
            <div class="stat-item">
              <div class="stat-label">窗口调整次数:</div>
              <div class="stat-value">{{ resizeCount }}</div>
            </div>
            <div class="stat-item">
              <div class="stat-label">键盘按键次数:</div>
              <div class="stat-value">{{ keyPressCount }}</div>
            </div>
            <div class="stat-item">
              <div class="stat-label">鼠标点击次数:</div>
              <div class="stat-value">{{ clickCount }}</div>
            </div>
          </div>
          <div class="text-sm text-gray-600 text-center">
            调整窗口大小、按键盘或点击来测试事件监听
          </div>
          <button @click="resetEventStats" class="btn-reset">重置统计</button>
        </div>
      </div>
    </div>

    <!-- 生命周期说明 -->
    <div class="mt-6 p-4 bg-purple-50 border border-purple-200 rounded">
      <h5 class="text-sm font-medium text-purple-800 mb-2">🔄 生命周期 Hook 说明</h5>
      <ul class="text-xs text-purple-700 space-y-1">
        <li>• <strong>onMounted</strong>: 组件挂载完成后执行，常用于初始化操作</li>
        <li>• <strong>onUnmounted</strong>: 组件卸载前执行，用于清理资源</li>
        <li>• <strong>onUpdated</strong>: 组件更新后执行，响应数据变化</li>
        <li>• <strong>onBeforeMount/onBeforeUnmount</strong>: 挂载/卸载前的准备工作</li>
        <li>• <strong>资源管理</strong>: 定时器、事件监听器等需要在卸载时清理</li>
      </ul>
    </div>
  </div>
</template>

<script setup lang="ts">
import {
  ref,
  onMounted,
  onUnmounted,
  onUpdated,
  onBeforeMount,
  onBeforeUnmount,
  nextTick,
} from 'vue'
import LifecycleChild from './LifecycleChild.vue'

// 生命周期日志
interface LifecycleLog {
  time: string
  type: string
  message: string
}

const lifecycleLogs = ref<LifecycleLog[]>([])

const addLog = (type: string, message: string) => {
  lifecycleLogs.value.push({
    time: new Date().toLocaleTimeString(),
    type,
    message,
  })

  // 限制日志数量
  if (lifecycleLogs.value.length > 20) {
    lifecycleLogs.value.shift()
  }
}

const getLogClass = (type: string) => {
  const classes = {
    onBeforeMount: 'log-before-mount',
    onMounted: 'log-mounted',
    onUpdated: 'log-updated',
    onBeforeUnmount: 'log-before-unmount',
    onUnmounted: 'log-unmounted',
    child: 'log-child',
  }
  return classes[type as keyof typeof classes] || ''
}

const clearLogs = () => {
  lifecycleLogs.value = []
}

// 动态组件控制
const showChild = ref(false)
const childCounter = ref(0)
const updateKey = ref(0)
let isUpdating = false

const forceUpdate = () => {
  updateKey.value++
  addLog('forceUpdate', '父组件强制更新')
}

const handleChildLifecycle = (event: { type: string; message: string }) => {
  addLog('child', `子组件: ${event.type} - ${event.message}`)
}

// 定时器管理
const timer = ref(0)
const isTimerRunning = ref(false)
let timerInterval: number | null = null

const startTimer = () => {
  if (!isTimerRunning.value) {
    isTimerRunning.value = true
    timerInterval = setInterval(() => {
      timer.value++
    }, 1000)
    addLog('timer', '定时器已启动')
  }
}

const stopTimer = () => {
  if (timerInterval) {
    clearInterval(timerInterval)
    timerInterval = null
    isTimerRunning.value = false
    addLog('timer', '定时器已停止')
  }
}

const resetTimer = () => {
  stopTimer()
  timer.value = 0
  addLog('timer', '定时器已重置')
}

// 事件监听器
const resizeCount = ref(0)
const keyPressCount = ref(0)
const clickCount = ref(0)

const handleResize = () => {
  resizeCount.value++
}

const handleKeyPress = () => {
  keyPressCount.value++
}

const handleClick = () => {
  clickCount.value++
}

const resetEventStats = () => {
  resizeCount.value = 0
  keyPressCount.value = 0
  clickCount.value = 0
  addLog('events', '事件统计已重置')
}

// 生命周期钩子
onBeforeMount(() => {
  addLog('onBeforeMount', '父组件即将挂载')
})

onMounted(() => {
  addLog('onMounted', '父组件已挂载')

  // 添加全局事件监听器
  window.addEventListener('resize', handleResize)
  window.addEventListener('keydown', handleKeyPress)
  window.addEventListener('click', handleClick)
})

onUpdated(() => {
  // 避免在更新过程中重复触发
  if (isUpdating) return

  isUpdating = true
  nextTick(() => {
    addLog('onUpdated', `父组件已更新 (updateKey: ${updateKey.value})`)
    isUpdating = false
  })
})

onBeforeUnmount(() => {
  addLog('onBeforeUnmount', '父组件即将卸载')

  // 清理定时器
  stopTimer()
})

onUnmounted(() => {
  addLog('onUnmounted', '父组件已卸载')

  // 清理事件监听器
  window.removeEventListener('resize', handleResize)
  window.removeEventListener('keydown', handleKeyPress)
  window.removeEventListener('click', handleClick)
})
</script>

<style scoped lang="scss">
.lifecycle-hook-demo {
  @apply bg-gray-50;
}

.lifecycle-section {
  @apply p-4 bg-white rounded-lg border border-gray-200;
}

.lifecycle-title {
  @apply text-base font-semibold text-gray-800 mb-4 pb-2 border-b border-gray-200;
}

.log-container {
  @apply bg-gray-900 rounded-lg p-3 max-h-48 overflow-y-auto mb-3;
}

.log-item {
  @apply text-sm mb-1 font-mono flex space-x-2;

  &.log-before-mount {
    @apply text-yellow-400;
  }

  &.log-mounted {
    @apply text-green-400;
  }

  &.log-updated {
    @apply text-blue-400;
  }

  &.log-before-unmount {
    @apply text-orange-400;
  }

  &.log-unmounted {
    @apply text-red-400;
  }

  &.log-child {
    @apply text-purple-400;
  }
}

.log-time {
  @apply text-gray-400 w-20;
}

.log-type {
  @apply w-24;
}

.log-message {
  @apply flex-1;
}

.btn-clear,
.btn-toggle,
.btn-update,
.btn-small,
.btn-start,
.btn-stop,
.btn-reset {
  @apply px-3 py-2 text-sm rounded font-medium transition-colors;
}

.btn-clear {
  @apply bg-gray-500 text-white hover:bg-gray-600;
}

.btn-toggle {
  &.btn-green {
    @apply bg-green-500 text-white hover:bg-green-600;
  }

  &.btn-red {
    @apply bg-red-500 text-white hover:bg-red-600;
  }
}

.btn-update {
  @apply bg-blue-500 text-white hover:bg-blue-600;
}

.btn-small {
  @apply bg-gray-200 text-gray-700 hover:bg-gray-300;
}

.btn-start {
  @apply bg-green-500 text-white hover:bg-green-600 disabled:opacity-50;
}

.btn-stop {
  @apply bg-red-500 text-white hover:bg-red-600 disabled:opacity-50;
}

.btn-reset {
  @apply bg-gray-500 text-white hover:bg-gray-600;
}

.child-container {
  @apply border-2 border-dashed border-gray-300 rounded-lg p-4 min-h-[100px] flex items-center justify-center;
}

.no-child {
  @apply text-gray-400 text-sm;
}

.timer-display {
  @apply flex items-center justify-center space-x-2;
}

.timer-value {
  @apply text-4xl font-bold text-blue-600;
}

.timer-label {
  @apply text-lg text-gray-600;
}

.event-stats {
  @apply grid grid-cols-3 gap-4;
}

.stat-item {
  @apply text-center;
}

.stat-label {
  @apply text-sm text-gray-600 mb-1;
}

.stat-value {
  @apply text-2xl font-bold text-blue-600;
}

// Vue 过渡动画
.fade-enter-active,
.fade-leave-active {
  transition: opacity 0.3s ease;
}

.fade-enter-from,
.fade-leave-to {
  opacity: 0;
}
</style>
